package workgroup.osaka;
import android.app.Activity;
import android.app.AlertDialog;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.media.AudioManager;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.CheckBox;
import android.widget.SeekBar;
import android.widget.SeekBar.OnSeekBarChangeListener;
import android.widget.TextView;
import android.widget.TimePicker;
import android.widget.TimePicker.OnTimeChangedListener;

/********************************************************************************
 * アラーム詳細画面クラス.
 * <p>
 * アラーム詳細画面クラスは以下の機能を有する
 * ・繰り返しダイアログ表示・設定
 * ・スヌーズダイアログ表示・設定
 * </p>
 ***********************************************************************************/
public class AlarmDetailActivity extends Activity {
    private final String TAG = "AlarmDetailyActivity"; 
    private AudioManager audioMng;
    private AlarmInfo ALARM_INFO;
    
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        // alarm_detail.xml の表示
        setContentView(R.layout.alarm_detail);
                
        // 音量の管理
        audioMng = (AudioManager)getSystemService(Context.AUDIO_SERVICE);
        final int MAX_SYSTEM_VOL = audioMng.getStreamMaxVolume(AudioManager.STREAM_ALARM);
        
        // 時刻表示
            // TODO キーボードから入力時の時刻設定 もしくは キーボードからの入力の抑制
            //timePickerを24h表記に変更
        TimePicker alarmTimePicker = (TimePicker)findViewById(R.id.almTime_timePicker);
        alarmTimePicker.setIs24HourView(true);
            // 時刻を設定した時に、アラーム時刻を更新
        OnTimeChangedListener alarmTimePickerListener = new OnTimeChangedListener() {
            public void onTimeChanged(TimePicker arg0, int hourOfDay, int minute) {
                ALARM_INFO.setAlarmTime(String.format("%1$02d:%2$02d",hourOfDay, minute));
                Log.v(TAG, "alarmTimePicker: "+ ALARM_INFO.getAlarmTime());
            }            
        };
        alarmTimePicker.setOnTimeChangedListener(alarmTimePickerListener);
        
        // 繰り返し設定ダイアログ表示
        OnClickListener repeatingAlarmListener = new OnClickListener() {
            public void onClick(View v) {
                repeatingAlarmDialog();
            }
        };
        findViewById(R.id.repeatingDay_layout).setOnClickListener(repeatingAlarmListener);
        
        // スヌーズ間隔設定ダイアログ表示
        OnClickListener snoozeIntervalListener = new OnClickListener() {
            public void onClick(View v) {
                snoozeIntervalDialog();
            }
        };
        findViewById(R.id.snoozeInterval_layout).setOnClickListener(snoozeIntervalListener);
        
        // 祝日鳴動
        OnClickListener holidayAlarmStopListener = new OnClickListener() {
            public void onClick(View view) {
                CheckBox checkBox = (CheckBox)view;
                ALARM_INFO.setHolidayAlarmStop(checkBox.isChecked());
            }   
        };
        findViewById(R.id.stopAlmOnHoliday_ckBtn).setOnClickListener(holidayAlarmStopListener);

        // アラーム音量
            // アラーム音量最大値をシステム音量の最大値に設定
        SeekBar alarmVolSeek = (SeekBar)findViewById(R.id.almVol_seekBar);
        alarmVolSeek.setMax(MAX_SYSTEM_VOL);
            // SeekBarイベントリスナーを登録
        OnSeekBarChangeListener alarmVolListener = new OnSeekBarChangeListener() {
            public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
            }
            public void onStartTrackingTouch(SeekBar seekBar) {
            }
            public void onStopTrackingTouch(SeekBar seekBar) {
                    // アラーム音量に値を登録する
                ALARM_INFO.setAlarmVol(seekBar.getProgress());
                Log.v(TAG, "alarmBolSeek: progress: "+ seekBar.getProgress());
            }
        };
        alarmVolSeek.setOnSeekBarChangeListener(alarmVolListener);

        // バイブレーション
        OnClickListener vibrationListener = new OnClickListener() {
            public void onClick(View view) {
                CheckBox checkBox = (CheckBox)view;
                ALARM_INFO.setVibration(checkBox.isChecked());
            }   
        };
        findViewById(R.id.onVib_ckBtn).setOnClickListener(vibrationListener);
        
        // 完了ボタン
        OnClickListener okBtnListener = new OnClickListener() {
            public void onClick(View v) {
                // インテント作成（通常画面遷移時に引き渡す値)  
                Intent intent = new Intent();   
                intent.putExtra("alarm", ALARM_INFO);            
                setResult(RESULT_OK, intent);
                // 画面戻る 
                finish();
            }
        };
        findViewById(R.id.ok_btn).setOnClickListener(okBtnListener);

        // キャンセルボタン
        OnClickListener cancelBtnListener = new OnClickListener() {
            public void onClick(View v) {
                Intent intent = new Intent();
                intent.putExtra("alarm", ALARM_INFO);
                setResult(RESULT_CANCELED, intent);
                finish();                
            }
        };
        findViewById(R.id.cancel_btn).setOnClickListener(cancelBtnListener);

        // Intentから画面遷移時のデータを取得
        // ・ALARM_INFOを登録
        Intent intent = getIntent();
        ALARM_INFO = (AlarmInfo)intent.getSerializableExtra("alarm");
        
        // Viewの表示を更新する
        updateView();
    }
    
    /****************************************************************************
     * 繰り返し設定ダイアログ.
     * <p>
     * スヌーズ間隔設定ダイアログを表示し、ダイアログで設定した曜日をアラーム情報に登録する
     * </p>
     ******************************************************************************/    
    private void repeatingAlarmDialog() {
    	// 繰り返しダイアログ チェックボックスの曜日配列
    	final CharSequence[] dayList = 
    		{getString(R.string.monday), getString(R.string.tuesday), getString(R.string.wednesday), getString(R.string.thursday),
    		 getString(R.string.friday), getString(R.string.saturday), getString(R.string.sunday)};
    	// チェック済み曜日配列を取得
        String repeatingDay = ALARM_INFO.getRepeatingDay();
        final boolean[] checkedItems = convertRepeatingDayStringToBoolean(repeatingDay);

    	// 繰り返しダイアログ生成
    	final AlertDialog.Builder repeatDlg = new AlertDialog.Builder(AlarmDetailActivity.this);
    	
    	//--------------------
    	// 繰り返しダイアログ設定
    	//--------------------
    			// タイトル
    	repeatDlg.setTitle(R.string.repeatingDay);
    	
    	    	// ダイアログ　チェックボックス処理
    	DialogInterface.OnMultiChoiceClickListener multiChoiceListener = new DialogInterface.OnMultiChoiceClickListener() {
    		public void onClick(DialogInterface dialog, int which,boolean isChecked) {
    			checkedItems[which]=isChecked;
    		}
    	};
    	repeatDlg.setMultiChoiceItems(dayList, checkedItems, multiChoiceListener);

    			// キャンセルボタン 処理
    	DialogInterface.OnClickListener cancelListener = new DialogInterface.OnClickListener() {
			public void onClick(DialogInterface dialog, int which) {
			}
		};
        repeatDlg.setNegativeButton(R.string.cancel, cancelListener);
		
                // OK 処理
        DialogInterface.OnClickListener okListener = new DialogInterface.OnClickListener() {
            public void onClick(DialogInterface dialog, int which) {
                    // アラーム情報の繰り返し曜日をダイアログで設定した曜日に変更する 
            	ALARM_INFO.setRepeatingDay(convertRepeatingDayBooleanToString(checkedItems));
            	    // 表示の更新
            	updateView();
            }
        };
		repeatDlg.setPositiveButton(R.string.ok, okListener);

		// 繰り返しダイアログ表示
    	repeatDlg.show();
    }
    
    /****************************************************************************
     * 繰り返し曜日をboolean配列に変換する.
     * <p>
     * 繰り返し曜日に存在する曜日は、繰り返す(true)、存在しない曜日は、繰り返さない(false)、<br>
     * と判断し、boolean配列に変換する
     * </p>
     * @param repeatingDay 月〜日の繰り返し曜日
     * @return 月〜日の繰り返し曜日
     ******************************************************************************/
    private boolean[] convertRepeatingDayStringToBoolean(String repeatingDay) {
    	boolean[] ret = { false, false, false, false, false, false, false };  // 月〜日の繰り返し設定の返値
    	char day;
    	
    	// 曜日テキストから繰り返す曜日を設定する
    	for ( int i=0; i<repeatingDay.length(); i++ ) {
    		day = repeatingDay.charAt(i);    		
    		if ( day == '月' ) ret[0] = true;
    		else if ( day == '火' ) ret[1] = true;
    		else if ( day == '水' ) ret[2] = true;
    		else if ( day == '木' ) ret[3] = true;
    		else if ( day == '金' ) ret[4] = true;
    		else if ( day == '土' ) ret[5] = true;
    		else if ( day == '日' ) ret[6] = true;
    		else if ( day == '　' ); // 何もしない
    		else {
    			// ここに入ってきたらおかしい
    			Log.w(TAG, "convartRepeatingTextStringToBoolean: " + "day=" + day);
    		}
    	}
    	return ret;
    }
    /****************************************************************************
     * boolean配列を繰り返し設定の曜日テキストに変換する
     * <p>
     * 繰り返す(true)、存在しない曜日は、繰り返さない(false)、のboolean配列を繰り返し設定の曜日テキストに変換する
     * </p>
     * @param 月〜日の繰り返し曜日 boolean配列
     * @return 月〜日の繰り返し曜日 String
     ******************************************************************************/
    private String convertRepeatingDayBooleanToString(boolean[] repeatingBool) {
        // 返値初期化
    	String repeatingDay = "";
    	
    	// boolean配列から曜日テキストを作成する
    	for ( int i=0; i<repeatingBool.length; i++ ) {  		
    		if ( repeatingBool[i] == true ) {
    			switch (i) {
    				case 0: repeatingDay += getString(R.string.mon); break;
    				case 1: repeatingDay += getString(R.string.tue); break;
    				case 2: repeatingDay += getString(R.string.wed); break;
    				case 3: repeatingDay += getString(R.string.thu); break;
    				case 4: repeatingDay += getString(R.string.fri); break;
    				case 5: repeatingDay += getString(R.string.sat); break;
	    			case 6: repeatingDay += getString(R.string.sun); break;
	    			default: 
	    				// ここに入ってきたらおかしい
	    				Log.w(TAG, "convertRepeatingDayBooleanToString: " + "i=" + i);
	    				break;
       			}
    		} else {
    			repeatingDay += "　";
    		}
    	}  	
    	// 繰り返し曜日を返す
    	return repeatingDay;
    }

    /****************************************************************************
     * スヌーズ間隔設定ダイアログ.
     * <p>
     * スヌーズ間隔設定ダイアログを表示し、スヌーズ間隔テキストをダイアログで設定した値に更新する
     * </p>
     ******************************************************************************/    
    private void snoozeIntervalDialog() {
    	// スヌーズ間隔設定ダイアログ ラジオボタンのスヌーズ間隔配列
    	final CharSequence[] snoozeList = 
    		{getString(R.string.oneMinute), getString(R.string.threeMinute), getString(R.string.fiveMinute),
    		 getString(R.string.tenMinute), getString(R.string.fifteenMinute)};

    	// ラジオボタンの選択状態を設定する
    	String snoozeIntervalTxt = Integer.toString(ALARM_INFO.getSnoozeInterval())+getString(R.string.minute);
    	//ラジオボタンのチェックボックスの初期位置設定
        int snoozeIndex;
        for(snoozeIndex = 0; snoozeIndex < snoozeList.length ; snoozeIndex++){
            Log.d(TAG, snoozeList[snoozeIndex] +""+snoozeIntervalTxt);
            if(snoozeList[snoozeIndex].equals(snoozeIntervalTxt)){
                break;
            }
        }
        int choiceItem = snoozeIndex;
    	
    	// スヌーズ間隔設定ダイアログ生成
    	final AlertDialog.Builder snoozeDlg = new AlertDialog.Builder(AlarmDetailActivity.this);

    	//--------------------
    	// 繰り返しダイアログ設定
    	//--------------------
    			// タイトル
    	snoozeDlg.setTitle(R.string.snoozeInterval);
    	
    	    	// ダイアログ　ラジオボタン処理
    	DialogInterface.OnClickListener clickListener = new DialogInterface.OnClickListener() {
    		public void onClick(DialogInterface dialog, int which) {
    		}
    	};
    	snoozeDlg.setSingleChoiceItems(snoozeList, choiceItem, clickListener);

    			// キャンセルボタン 処理
    	DialogInterface.OnClickListener cancelListener = new DialogInterface.OnClickListener() {
			public void onClick(DialogInterface dialog, int which) {
			}
		};
        snoozeDlg.setNegativeButton(R.string.cancel, cancelListener);
		
                // OK 処理
        DialogInterface.OnClickListener okListener = new DialogInterface.OnClickListener() {
            public void onClick(DialogInterface dialog, int which) {
                        // 選択中のスヌーズ間隔をアラーム情報に設定
                int index = ((AlertDialog)dialog).getListView().getCheckedItemPosition();
                String snoozeIntervalStr = (String)((AlertDialog)dialog).getListView().getItemAtPosition(index);
                int snoozeInterval = Integer.valueOf(snoozeIntervalStr.replaceAll(getString(R.string.minute), ""));
                ALARM_INFO.setSnoozeInterval(snoozeInterval);
                        // 表示の更新
                updateView();
            }
        };
		snoozeDlg.setPositiveButton(R.string.ok, okListener);

		// スヌーズ間隔設定ダイアログ表示
    	snoozeDlg.show();
    }
    
    /****************************************************************************
     * アラーム情報に従ってView更新する.
     ******************************************************************************/      
    private void updateView() {
        // アラーム情報(ALARM_INFO)を取得
        AlarmInfo info = ALARM_INFO;
        
        // アラーム情報をViewに表示する
            // 時刻設定
        TimePicker timePicker = (TimePicker)findViewById(R.id.almTime_timePicker);
        String[] alarmTime = info.getAlarmTime().split(":");
        timePicker.setCurrentHour(Integer.parseInt(alarmTime[0]));
        timePicker.setCurrentMinute(Integer.parseInt(alarmTime[1]));        
            // 繰り返し設定
        TextView repeatingDayText = (TextView)findViewById(R.id.repeatingDay_txt);
        repeatingDayText.setText(info.getRepeatingDay());
            // スヌーズ間隔設定
        TextView snoozeIntervalText = (TextView)findViewById(R.id.snoozeInterval_txt);
        snoozeIntervalText.setText(Integer.toString(info.getSnoozeInterval())+getString(R.string.minute));
            // 祝日鳴動設定
        CheckBox holidayAlarmStopCheck = (CheckBox)findViewById(R.id.stopAlmOnHoliday_ckBtn);
        holidayAlarmStopCheck.setChecked(info.getHolidayAlarmStop());
            // アラーム音量
        SeekBar alarmVolSeek = (SeekBar)findViewById(R.id.almVol_seekBar);
        alarmVolSeek.setProgress(info.getAlarmVol());
            // バイブレーション設定
        CheckBox vibrationCheck = (CheckBox)findViewById(R.id.onVib_ckBtn);
        vibrationCheck.setChecked(info.getVibration());
    }
}